feat(persona-kit): typed persona.ts authoring that compiles to persona.json#138
feat(persona-kit): typed persona.ts authoring that compiles to persona.json#138khaliqgant wants to merge 1 commit into
Conversation
…a.json
Add definePersona() + typed authoring types in persona-kit, giving
IDE autocomplete for integration trigger event names across all five
known providers (github, linear, slack, notion, jira) via the existing
KNOWN_TRIGGERS registry. The `KnownTriggerName<P> | (string & {})`
pattern keeps off-registry events and unknown providers valid, so the
runtime stays the source of truth.
Add an `agentworkforce persona compile <persona.ts>` CLI command that
esbuild-bundles the file, imports the default export, validates it with
parsePersonaSpec, and writes the raw authored spec to a sibling
persona.json. persona.json remains the runtime artifact — loaders and
the deploy bundler are unchanged.
Convert examples/review-agent to persona.ts as the demo (regenerated
persona.json is semantically identical) and add tests for the typed
helper and the compiler round-trip.
Implemented by codex-2; reviewed and verified (persona-kit + cli tests,
root typecheck incl. examples) before commit.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
📝 WalkthroughWalkthroughThis pull request adds a TypeScript-based persona authoring system and CLI compilation pipeline. It introduces typed contracts for defining personas with handler or interactive modes, a bundler that compiles TypeScript persona definitions to JSON, and an example review-agent persona demonstrating GitHub and Slack integration triggers with Claude model configuration. ChangesPersona Authoring and Compilation
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Poem
🚥 Pre-merge checks | ✅ 4 | ❌ 1❌ Failed checks (1 warning)
✅ Passed checks (4 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
1 issue found across 10 files
Prompt for AI agents (unresolved issues)
Check if these issues are valid — if so, understand the root cause of each and fix them. If appropriate, use sub-agents to investigate and fix each issue separately.
<file name="packages/persona-kit/src/define.ts">
<violation number="1" location="packages/persona-kit/src/define.ts:83">
P2: This helper skips excess-property checking, so typos in `persona.ts` can compile and be silently discarded later. Make the authoring surface exact (or require `satisfies` at the call site) so unknown fields fail fast.</violation>
</file>
Reply with feedback, questions, or to request a fix.
Re-trigger cubic
| | InteractivePersonaDefinition | ||
| | HandlerPersonaDefinition; | ||
|
|
||
| export function definePersona<const T extends PersonaDefinition>(input: T): T { |
There was a problem hiding this comment.
P2: This helper skips excess-property checking, so typos in persona.ts can compile and be silently discarded later. Make the authoring surface exact (or require satisfies at the call site) so unknown fields fail fast.
Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. At packages/persona-kit/src/define.ts, line 83:
<comment>This helper skips excess-property checking, so typos in `persona.ts` can compile and be silently discarded later. Make the authoring surface exact (or require `satisfies` at the call site) so unknown fields fail fast.</comment>
<file context>
@@ -0,0 +1,85 @@
+ | InteractivePersonaDefinition
+ | HandlerPersonaDefinition;
+
+export function definePersona<const T extends PersonaDefinition>(input: T): T {
+ return input;
+}
</file context>
What
Lets authors write a typed
persona.tsinstead of hand-writingpersona.json, with full IDE autocomplete — including integration trigger event names.Then:
agentworkforce persona compile examples/review-agent/persona.ts→ writes the siblingpersona.json.Trigger typing — not a cap at 5
The
onfield is typedKnownTriggerName<P> | (string & {}), and the integrations map has a string index signature. That means any provider key and any event string already type-check — the runtime /lintTriggersstay the source of truth (an unknown event is a lint warning, never a type error).What's typed today is just where autocomplete suggestions exist: the curated
KNOWN_TRIGGERSregistry, which currently covers the Tier-1 providers (github, linear, slack, notion, jira). The platform supports webhooks across many more integrations — those keys/events are fully usable now, they just don't surface autocomplete yet.Follow-up (separate PR): codegen
KNOWN_TRIGGERSfrom the canonical adapter event catalogs inrelayfile-adapters(~40 providers) so autocomplete covers the full webhook surface and stays in sync. Tracked separately; this PR delivers the typed-authoring mechanism and the curated baseline.How
definePersona()+ typed authoring types inpackages/persona-kit/src/define.ts(exported from the barrel). Per-provider trigger autocomplete is driven off theKNOWN_TRIGGERSregistry.agentworkforce persona compile <persona.ts>(packages/cli/src/persona-compile.ts) esbuild-bundles the file, imports the default export, validates it withparsePersonaSpec, and writes the raw authored spec to a siblingpersona.json(raw, not the normalized parse output — preserves parity with hand-authored JSON).persona.jsonstays the runtime artifact. Loaders (local-personas.ts) and the deploy bundler (bundle.ts,require('./persona.json')) are unchanged —persona.tsis purely an authoring layer that compiles down.esbuildis added to theclipackage only; the publishedpersona-kitstays dependency-light.examples/review-agentconverted topersona.tsas the demo (regeneratedpersona.jsonis semantically identical) and wired intotypecheck:examples.Tests
Verification
pnpm -C packages/persona-kit test(223) ·pnpm -C packages/cli test(202) · rootpnpm typecheckincl.typecheck:examples— all green.Implemented by codex-2 and reviewed before merge.
🤖 Generated with Claude Code